package com.anolesoft.yr.mbus.base.controller;

import com.anolesoft.common.core.web.domain.AjaxResult;
import com.anolesoft.yr.mbus.base.dto.BaseRegionDTO;
import com.anolesoft.yr.mbus.base.dto.BaseRegionTreeQueryDTO;
import com.anolesoft.yr.mbus.base.service.BaseRegionService;
import com.anolesoft.yr.mbus.base.vo.BaseRegionTreeVO;
import com.anolesoft.yr.mbus.base.vo.BaseRegionVO;
import com.anolesoft.yr.util.*;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;

/**
 * @author zhj
 * @date 2020/8/7 19:32
 */
@RestController()
public class BaseRegionController {
    @Autowired
    private BaseRegionService baseRegionService;

    @PostMapping(value = "/api/base/region/add", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult create(BaseRegionVO baseRegionVO) {
        BaseRegionDTO baseRegionDTO = BaseRegionDTO.builder()
                .createUserUid(SecurityUtils.getUserId())
                .deleteFlag(Boolean.FALSE)
                .factoryCode(SecurityUtils.getFactoryCode())
                .modifyUserUid(SecurityUtils.getUserId())
                .objuid(CommonUtils.fastUUID())
                .parentUid(baseRegionVO.getParentUid())
                .regionCode(baseRegionVO.getRegionCode())
                .regionLevel(baseRegionVO.getRegionLevel())
                .regionName(baseRegionVO.getRegionName())
                .remark(baseRegionVO.getRemark())
                .build();
        return new AjaxResult(HttpStatus.SUCCESS, Constants.CREATE_SUCCESS_MESSAGE, baseRegionService.create(baseRegionDTO));
    }

    @PutMapping(value = "/api/base/region/update", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult modify( BaseRegionVO baseRegionVO) {
        BaseRegionDTO baseRegionDTO = BaseRegionDTO.builder()
                .factoryCode(baseRegionVO.getFactoryCode())
                .modifyUserUid(SecurityUtils.getUserId())
                .objuid(baseRegionVO.getObjuid())
                .parentUid(baseRegionVO.getParentUid())
                .regionCode(baseRegionVO.getRegionCode())
                .regionLevel(baseRegionVO.getRegionLevel())
                .regionName(baseRegionVO.getRegionName())
                .remark(baseRegionVO.getRemark())
                .build();
        return new AjaxResult(HttpStatus.SUCCESS, Constants.MODIFY_SUCCESS_MESSAGE, baseRegionService.modify(baseRegionDTO));
    }

    @DeleteMapping(value = "/api/base/region/delete/{id}", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult remove(@PathVariable("id") String id) {
        return new AjaxResult(HttpStatus.SUCCESS, Constants.DELETE_SUCCESS_MESSAGE, baseRegionService.remove(id));
    }
    @DeleteMapping(value = "/api/base/region/delete", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult removeBatch(@RequestParam("ids[]") List<String> ids) {
//        System.out.println(ids);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.DELETE_SUCCESS_MESSAGE, baseRegionService.removeBatch(ids));
    }

    @GetMapping(value = "/api/base/region/list/all", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectAll() {
        List<BaseRegionVO> vos = baseRegionService.selectAll().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(vos.size(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

//    @GetMapping(value = "/api/base/region/list/treegrid", produces = MediaType.APPLICATION_JSON_VALUE)
//    public CommonResultDemo<List<BaseRegionVO>> selectAllForTreeGrid() {
//        List<BaseRegionVO> vos = baseRegionService.selectAll().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
//        vos.stream().forEach(t->{
//            if (t.getParentUid().equals("-")) {
//                t.setParentUid("0");
//            }
//        });
//        return new CommonResultDemo<>(0, Constants.QUERY_SUCCESS_MESSAGE, vos, vos.size(), true, "操作成功！");
//    }
//@GetMapping(value = "/api/base/region/list/treegrid", produces = MediaType.APPLICATION_JSON_VALUE)
//public CommonResultDemo<List<TreeGrid>> selectAllForTreeGrid() {
//    List<TreeGrid> vos = baseRegionService.selectAll().stream().map(t-> new TreeGrid(
//            t.getParentUid().equals("-")?"0":t.getParentUid(),
//            t.getObjuid(),
//            t.getRegionName(),
//            t.getRegionName(),
//            t.getRegionCode(),
//            t.getRegionLevel()
//    )).collect(Collectors.toList());
//
//    return new CommonResultDemo<>(0, Constants.QUERY_SUCCESS_MESSAGE, vos, vos.size(), true, "操作成功！");
//}
    @AllArgsConstructor
    @Data
    @NoArgsConstructor
    public static class TreeGrid{
        private String pid;
        private String id;
        private String name;
        private String regionName;
        private String regionCode;
        private String regionLevel;
    }
//    public class CommonResultDemo<T>{
//        private Integer code;
//        private String msg;
//        private T data;
//        private Integer count;
//        private Boolean is;
//        private String tip;
//        public CommonResultDemo(){}
//        public CommonResultDemo(Integer code,String msg,T data, Integer count, Boolean is,String tip){
//            this.code = code;
//            this.msg = msg;
//            this.data = data;
//            this.count = count;
//            this.is = is;
//            this.tip = tip;
//        }
//    }

    @GetMapping(value = "/api/base/region/list/all/page", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectPageAll(
            @RequestParam("rows") Integer limit,
            @RequestParam("page") Integer page) {
//        List<BaseRegionVO> vos = baseRegionService.selectAll(limit, page).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
//        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, vos.size(), vos);

        PageData<List<BaseRegionDTO>> pageData = this.baseRegionService.selectAll(limit, page);
        List<BaseRegionVO> vos = pageData.getItems().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, pageData.getTotal(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    private BaseRegionVO dto2vo(BaseRegionDTO t) {
        return BaseRegionVO.builder()
                .createUserUid(t.getCreateUserUid())
                .deleteFlag(t.getDeleteFlag())
                .factoryCode(t.getFactoryCode())
                .modifyUserUid(t.getModifyUserUid())
                .objuid(t.getObjuid())
                .parentUid(t.getParentUid())
                .regionCode(t.getRegionCode())
                .regionLevel(t.getRegionLevel())
                .regionName(t.getRegionName())
                .remark(t.getRemark())
                .createTime(t.getCreateTime())
                .modifyTime(t.getModifyTime())
                .build();
    }

    @GetMapping(value = "/api/base/region/get/{id}", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectOneById(@PathVariable("id") String id) {
        Optional<BaseRegionDTO> baseRegionDTO = this.baseRegionService.selectOneById(id);
        if (baseRegionDTO.isPresent()) {
            return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, dto2vo(baseRegionDTO.get()));
        } else {
            return new AjaxResult(HttpStatus.NOT_FOUND, Constants.QUERY_SUCCESS_MESSAGE, null);
        }

    }

    @GetMapping(value = "/api/base/region/list/name", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectListByName(
            @RequestParam("regionName") String regionName) {
        List<BaseRegionVO> vos = this.baseRegionService.selectListByName(regionName).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(vos.size(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/name/page", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectListByName(
            @RequestParam("regionName") String regionName,
            @RequestParam("rows") Integer limit,
            @RequestParam("page") Integer page) {
//        List<BaseRegionVO> vos = this.baseRegionService.selectPageByName(regionName, limit, page).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
//        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, vos.size(), vos);

        PageData<List<BaseRegionDTO>> pageData = this.baseRegionService.selectPageByName(regionName, limit, page);
        List<BaseRegionVO> vos = pageData.getItems().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, pageData.getTotal(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/factorycode", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectListByFactoryCode(@RequestParam("factoryCode") String factoryCode) {
        List<BaseRegionVO> vos = this.baseRegionService.selectListByFactoryCode(factoryCode).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(vos.size(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/factorycod/page", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectListByFactoryCode(
            @RequestParam("regionCode") String regionCode,
            @RequestParam("rows") Integer limit,
            @RequestParam("page") Integer page) {
//        List<BaseRegionVO> vos = this.baseRegionService.selectPageByFactoryCode(regionCode, limit, page).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
//        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, vos.size(), vos);
        PageData<List<BaseRegionDTO>> pageData = this.baseRegionService.selectPageByFactoryCode(regionCode, limit, page);
        List<BaseRegionVO> vos = pageData.getItems().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, pageData.getTotal(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/condition", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectListByCondition(BaseRegionVO baseRegionVO) {
        BaseRegionDTO baseRegionDTO = BaseRegionDTO.builder()
                .regionName(baseRegionVO.getRegionName())
                .regionLevel(baseRegionVO.getRegionLevel())
                .regionCode(baseRegionVO.getRegionCode())
                .parentUid(baseRegionVO.getParentUid())
                .factoryCode(baseRegionVO.getFactoryCode())
                .build();
//        Integer limit = baseRegionVO.getLimit();
//        Integer page = baseRegionVO.getpage();
        List<BaseRegionVO> vos = this.baseRegionService.selectListByCondition(baseRegionDTO).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(vos.size(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/condition/page", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult selectListByConditionPage(BaseRegionVO baseRegionVO) {
        BaseRegionDTO baseRegionDTO = BaseRegionDTO.builder()
                .regionName(baseRegionVO.getRegionName())
                .regionLevel(baseRegionVO.getRegionLevel())
                .regionCode(baseRegionVO.getRegionCode())
                .parentUid(baseRegionVO.getParentUid())
                .factoryCode(baseRegionVO.getFactoryCode())
                .build();
        Integer limit = baseRegionVO.getRows();
        Integer page = baseRegionVO.getPage();
//        List<BaseRegionVO> vos = this.baseRegionService.selectPageByCondition(baseRegionDTO, limit, page).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
//        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, vos.size(), vos);
        PageData<List<BaseRegionDTO>> pageData = this.baseRegionService.selectPageByCondition(baseRegionDTO, limit, page);
        List<BaseRegionVO> vos = pageData.getItems().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(limit, pageData.getTotal(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/tree/{parentUid}", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult findChildrenByParentUid(@PathVariable("parentUid") String parentUid) {
        List<BaseRegionVO> vos = this.baseRegionService.findChildrenByParentUid(parentUid).stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(vos.size(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, pageInfo);
    }

    @GetMapping(value = "/api/base/region/list/tree", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult findTopLevel() {
        List<BaseRegionVO> vos = this.baseRegionService.findTopLevel().stream().map(t -> dto2vo(t)).collect(Collectors.toList());
        //PageInfo<List<BaseRegionVO>> pageInfo = new PageInfo<>(vos.size(), vos);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, vos);
    }

    @GetMapping(value = "/api/base/region/list/tree/all", produces = MediaType.APPLICATION_JSON_VALUE)
    public AjaxResult getTree(HttpServletRequest request) {
        System.out.println(request.getHeader("token"));
        List<BaseRegionTreeQueryDTO> baseRegionTreeQueryDTOS = baseRegionService.getTree("-");

        List<BaseRegionTreeVO> vos = buildVos(baseRegionTreeQueryDTOS);
        return new AjaxResult(HttpStatus.SUCCESS, Constants.QUERY_SUCCESS_MESSAGE, vos);
    }
    private List<BaseRegionTreeVO> buildVos(List<BaseRegionTreeQueryDTO> baseRegionTreeQueryDTOS) {
        return baseRegionTreeQueryDTOS.stream().map(t->{
            BaseRegionTreeVO vo = BaseRegionTreeVO.builder()
//                    .field(t.getField())
                    .id(t.getId())
//                    .title(t.getTitle())
//                    .href(t.getHref())
                    //.pid(t.getPid().equals("-") ? null : t.getPid())
                    .pid(t.getPid())
                    .treeName(t.getTitle())
                    .regionCode(t.getRegionCode())
                    .regionLevel(t.getRegionLevel())
                    .regionName(t.getRegionName())
                    .factoryCode(t.getFactoryCode())
                    .name(t.getRegionName())
                    .build();
            if(t.getChildren().size()>0){
                vo.setChildren( buildVos(t.getChildren()) );
//                vo.setTreeList(buildVos(t.getChildren()));
            }else{
                vo.setChildren(new ArrayList<>(10));
//                vo.setTreeList(new ArrayList<>(10));
            }
            return vo;
        }).collect(Collectors.toList());
    }

}
